package com.ccloud.file.controller;

import cn.hutool.core.io.FileUtil;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.ccloud.api.file.domain.FileAtta;
import com.ccloud.api.file.dto.PreviewFile;
import com.ccloud.api.file.service.IFileAttaService;
import com.ccloud.common.core.reqres.response.R;
import com.ccloud.common.core.utils.CollectionUtils;
import com.ccloud.common.core.utils.StringUtils;
import com.ccloud.common.core.utils.ValueUtils;
import com.ccloud.common.minio.properties.MinioProperties;
import com.ccloud.common.minio.template.MinioTemplate;
import com.google.common.collect.Lists;
import io.minio.StatObjectResponse;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.io.IOUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.multipart.MultipartFile;

import javax.annotation.Resource;
import javax.servlet.http.HttpServletResponse;
import java.io.InputStream;
import java.net.URLEncoder;
import java.text.SimpleDateFormat;
import java.util.Arrays;
import java.util.Date;
import java.util.List;
import java.util.UUID;
import java.util.stream.Collectors;

/**
 * <p>
 * 文件控制器
 * </p>
 *
 * @author chentl
 * @since 2018-11-30
 */
@Slf4j
@RequestMapping("/atta")
@RestController
public class FileController {


    @Autowired
    private MinioTemplate minioTemplate;

    @Resource
    private IFileAttaService fileService;

    /**
     * 上传文件
     */
    @PostMapping("/upload")
    public R uploadByMinio(MultipartFile file) throws Exception {
        if (file.getSize() < 1) {
            log.warn("文件大小为：0");
            return R.fail("文件大小为：0");
        }
        String fileName = file.getOriginalFilename();
        String fileType = FileUtil.extName(fileName);
        String randomName = UUID.randomUUID() + "." + fileType;


        InputStream inputStream = file.getInputStream();
        String contentType = file.getContentType();
        String objectName = prefixDate() + "/" + randomName;

        minioTemplate.putObject(MinioProperties.bucketName, objectName, inputStream, file.getSize(), contentType);

        log.info("[file]bucketName:{} objectName:{} contentType:{} 上传成功!", MinioProperties.bucketName, objectName, contentType);
        StatObjectResponse objectInfo = minioTemplate.getObjectInfo(MinioProperties.bucketName, objectName);
        String downloadUrl = minioTemplate.getObjectURL(MinioProperties.bucketName, objectName);

        // 保存数据到 文件表
        FileAtta fileAtta = FileAtta.builder()
                .filePath(objectInfo.object())
                .fileType(fileType)
                .originalName(fileName)
                .randomName(randomName)
                .downloadUrl(downloadUrl)
                .build();

        fileService.save(fileAtta);

        return R.ok(fileAtta, "上传成功!");
    }

    @GetMapping("/get-uploaded-files")
    public R<Object> getUploadedFiles(String attaIds) {
        if (StringUtils.isBlank(attaIds)) {
            return R.ok(Lists.newArrayList());
        }

        List<String> ids = Arrays.asList(attaIds.split(","));

        List<FileAtta> fileAttas = fileService.list(new LambdaQueryWrapper<FileAtta>().eq(FileAtta::getDelFlag, 0).in(FileAtta::getId, ids));

        List<PreviewFile> previewFiles = Lists.newArrayList();
        if (CollectionUtils.isNotEmpty(fileAttas)) {
            previewFiles = fileAttas.stream().map(fileAtta -> PreviewFile.builder()
                    .id(ValueUtils.parseString(fileAtta.getId()) )
                    .uid(fileAtta.getRandomName())
                    .name(fileAtta.getOriginalName())
                    .status("done")
                    .thumbUrl(fileAtta.getDownloadUrl())
                    .url(fileAtta.getDownloadUrl())
                    .build())
                    .collect(Collectors.toList());
        }

        return R.ok(previewFiles);
    }

    /**
     * 下载文件
     */
    @GetMapping("/download/download-by-name")
    public void download(String fileName, HttpServletResponse response) throws Exception {
        final StatObjectResponse stat = minioTemplate.getObjectInfo(MinioProperties.bucketName, fileName);
        response.setContentType(stat.contentType());
        response.setCharacterEncoding("UTF-8");
        response.setHeader("Content-Disposition", "attachment;filename=" + URLEncoder.encode(fileName, "UTF-8"));
        InputStream is = minioTemplate.getObject(MinioProperties.bucketName, fileName);
        IOUtils.copy(is, response.getOutputStream());
        is.close();
    }

    /**
     * 获取文件前缀
     *
     * @return 返回上传路径
     */
    private String prefixDate() {
        //文件路径
        SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd");
        return sdf.format(new Date());
    }

}
